require 'yaml'
require 'simple-json'
class MorphologicalAnalysedTextEncoder
  @@cashe = Array.new
  
  def self.init
    corpus_info = YAML.load_file("config/corpus_info.yml")
    keys = corpus_info["tags"]
    @@split_word = corpus_info["split_word"]
    if corpus_info.has_key? "BOS"
      @@bos = corpus_info["BOS"]["key"]
      @@bos_index = corpus_info["BOS"]["index"]
    end
    if corpus_info.has_key? "EOS"
      @@eos = corpus_info["EOS"]["key"]
      @@eos_index = corpus_info["EOS"]["index"]
      @@eos_line = corpus_info["EOS"].has_key?("line") ? corpus_info["EOS"]["line"] : false
    end
    @@tags = YAML.load_file("config/split_tags.yml")
    @@invert_tags = @@tags.invert
    @@enable_tags = keys.map{|key| @@tags[key] }
    @@json_builder = JsonBuilder.new
    if corpus_info.has_key?("BOS") && corpus_info.has_key?("EOS")
      @@process = Proc.new{|line| case1(line)}
    elsif corpus_info.has_key?("BOS") && !corpus_info.has_key?("EOS")
      @@process = Proc.new{|line| case2(line)}
    elsif !corpus_info.has_key?("BOS") && corpus_info.has_key?("EOS")
      @@process = Proc.new{|line| case3(line)}
    else
      @@process = Proc.new{ 
        puts "config error: non eos & bos tag"
        exit(false)
      }
    end
  end
  
  def self.cashe(line)
    @@process.call(line)
  end
  
  def self.case1(line)
    columns = line.split(@@split_word)
    word = Hash[*(@@enable_tags.zip(columns).flatten)]
    word.delete(nil)
    @@cashe.clear if columns[@@bos_index] == @@bos
    if columns[@@eos_index] == @@eos
      @@cashe << word unless @@eos_line
      regist
    else
      @@cashe << word
    end
  end
  
  def self.case2(line)
    columns = line.split(@@split_word)
    word = Hash[*(@@enable_tags.zip(columns).flatten)]
    word.delete(nil)
    if columns[@@bos_index] == @@bos && !@@cashe.empty?
      regist
    end
    @@cashe << word   
  end
  
  def self.case3(line)
    columns = line.split(@@split_word)
    word = Hash[*(@@enable_tags.zip(columns).flatten)]
    word.delete(nil)
    if columns[@@eos_index] == @@eos
      @@cashe << word unless @@eos_line
      regist
    else
      @@cashe << word
    end     
  end
  
  private
  def self.regist
    data = @@cashe.map{|word|
      @@enable_tags.map{|key| word[key].blank? ? nil : "#{key}#{word[key]}"}.compact.join + "\t"
    }.join
    json = @@cashe.map{|word|
      compact_word = word.delete_if {|key, value| value.blank? }
      json_word = Hash.new
      compact_word.each{|key,value| json_word[@@invert_tags[key]] = value}
      json_word
    }
    text = @@cashe.map{|word| word[@@tags["surface"]] }
    Corpus.create(
      :text => text.join(""),
      :sequence => text.join(" "),
      :data => data,
      :json => @@json_builder.build(json)
    )
    @@cashe.clear
  end
end